package yawning.mew;

import java.lang.reflect.Constructor;

import org.apache.commons.math.random.RandomGenerator;

public class MewPRNG {
	RandomGenerator mRandomGenerator;

	@SuppressWarnings("rawtypes")
	public MewPRNG(String generator, int seed) {
		try {
			Class<?> c = Class.forName(generator);

			if (RandomGenerator.class.isAssignableFrom(c)) {
				Constructor ctor = (Constructor) c.getDeclaredConstructor(new Class[] { java.lang.Integer.TYPE });

				mRandomGenerator = (RandomGenerator) ctor.newInstance(seed);
			}
		} catch (Exception e) { throw new RuntimeException(e); }
	}

	public double nextDouble() {
		return mRandomGenerator.nextDouble();
	}

	public boolean nextBoolean() {
		return mRandomGenerator.nextBoolean();
	}

	public double nextGaussian() {
		return mRandomGenerator.nextGaussian();
	}

	public int nextInt(int n) {
		return mRandomGenerator.nextInt(n);
	}

	// This was included in MersenneTwisterFast, but it's a non-standard extension.
	// Naturally the Mew code uses it all over the place.
	public boolean nextBoolean(double p) {
		if (p > 1.0 || p < 0.0) {
			throw new IllegalArgumentException("Probability must fall between 0.0 and 1.0: " + p);
		}

		if (p == 0.0) return false; else if (p == 1.0) return true;

		return mRandomGenerator.nextDouble() < p;
	}
}
